;CODE FROM http://wiki.osdev.org/Barebones
global loader           ; making entry point visible to linker
extern kmain            ; kmain is defined elsewhere

jmp near stage2

; setting up the Multiboot header - see GRUB docs for details
MODULEALIGN equ  1<<0                   ; align loaded modules on page boundaries
MEMINFO     equ  1<<1                   ; provide memory map
FLAGS       equ  MODULEALIGN | MEMINFO  ; this is the Multiboot 'flag' field
MAGIC       equ    0x1BADB002           ; 'magic number' lets bootloader find the header
CHECKSUM    equ -(MAGIC + FLAGS)        ; checksum required

section .text

;ok... this might be a bit hackish but...
;the kernel is loaded somewhre up 0x7C00, so all code needs to point exactly to it (boring)
;or we could tell the linker to update our references (good)
;but some memory address (video and I/O ports, are relative to 0x0
;so we will move the kernel down there and start executing it there

;to make things interesting and to know when stop copying the kernel will contain
;the string "??????????????" at the end of file ^_^
	
stage2:
;	xor edx, edx	;we will use edx to count how many bytes we have copyed alreay
;	mov esi, go_on+0x9200
;	.loop:
;		mov edi, end+0x9200	;go_on was updated on the movsw, so it points to the right position already
;		cmpsw
;		je near .done
;		sub esi, 2		;the comparison put esi 2 bytes up, move it back
;		mov edi, edx	;edx = bytes copied, since we start at zero, this is pos to copy the next byte
;		add edx, 2		;we have move another two bytes, YAY
;		jmp near .loop

	mov esi, loader+0x9200
	mov edi, 0
	mov ecx, 0xF000	
	rep movsb
		
	jmp 0x0	;now that the kernel is down there, go there and go on living...

;This is the multiboot header. Everything beloow here should work on GRUB
align 4
MultiBootHeader:
   dd MAGIC
   dd FLAGS
   dd CHECKSUM

; reserve initial kernel stack space
STACKSIZE equ 0x4000                  ; that's 16k.

loader:
   mov esp, stack+STACKSIZE           ; set up the stack
   push eax                           ; pass Multiboot magic number
   push ebx                           ; pass Multiboot info structure

   call  kmain                       ; call kernel proper
   hlt                                ; halt machine should kernel return

section .bss
align 32
stack:
   resb STACKSIZE                     ; reserve 16k stack on a quadword boundary

